import { Injectable } from '@nestjs/common';
import Dysmsapi20170525, * as $Dysmsapi20170525 from '@alicloud/dysmsapi20170525';
import * as $OpenApi from '@alicloud/openapi-client';
import Util, * as $Util from '@alicloud/tea-util';
import { randomAuthCode } from '../../util';
import {
  ACCESS_KEY_ID,
  ACCESS_KEY_SECRET,
  SIGN_NAME,
  TEMPLATE_CODE,
} from '../../constant';
import { UserService } from '../user/user.service';
import dayjs from 'dayjs';
import { Result } from '../../dto/result.type';

@Injectable()
export class AuthService {
  constructor(private readonly userService: UserService) {}

  static createClient(
    accessKeyId: string,
    accessKeySecret: string,
  ): Dysmsapi20170525 {
    const config = new $OpenApi.Config({
      // 必填，您的 AccessKey ID
      accessKeyId: accessKeyId,
      // 必填，您的 AccessKey Secret
      accessKeySecret: accessKeySecret,
    });
    // Endpoint 请参考 https://api.aliyun.com/product/Dysmsapi
    config.endpoint = `dysmsapi.aliyuncs.com`;
    return new Dysmsapi20170525(config);
  }

  async sendAuthCode(tel: string): Promise<Result> {
    const user = await this.userService.findUserByTel(tel);
    // 发送验证码间隔不超过 60s
    if (user) {
      const diffTime = dayjs().diff(dayjs(user.codeCreateAt));
      if (diffTime < 1000 * 60)
        return {
          code: false,
          message: '发送验证码间隔低于 60s，请稍后重试',
        };
    }
    const code = randomAuthCode();
    const client = AuthService.createClient(ACCESS_KEY_ID, ACCESS_KEY_SECRET);
    const sendSmsRequest = new $Dysmsapi20170525.SendSmsRequest({
      signName: SIGN_NAME,
      templateCode: TEMPLATE_CODE,
      phoneNumbers: tel,
      templateParam: `{"code":${code}}`,
    });
    const runtime = new $Util.RuntimeOptions({});
    try {
      await client.sendSmsWithOptions(sendSmsRequest, runtime);
      if (user) {
        return await this.userService.updateUserCode(user.id, code);
      } else {
        return await this.userService.createUser({
          tel,
          code,
          codeCreateAt: new Date(),
        });
      }
    } catch (error) {
      console.log(error);
      // 如有需要，请打印 error
      Util.assertAsString(error.message);
      return {
        code: false,
        message: error.message,
      };
    }
  }
}
